package com.fowo.api.datainterface.service.impl.implCore;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.convert.Convert;
import cn.hutool.core.exceptions.ExceptionUtil;
import cn.hutool.core.lang.Assert;
import cn.hutool.core.lang.UUID;
import cn.hutool.core.lang.func.Func1;
import cn.hutool.core.map.MapUtil;
import cn.hutool.core.util.*;
import cn.hutool.http.webservice.SoapClient;
import cn.hutool.http.webservice.SoapProtocol;
import cn.hutool.http.webservice.SoapUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.dynamic.datasource.annotation.DS;
import com.fowo.api.datainterface.aspect.BaseAspect;
import com.fowo.api.datainterface.constants.Constants;
import com.fowo.api.datainterface.constants.DataTypeKind;
import com.fowo.api.datainterface.model.DataContextModel;
import com.fowo.api.datainterface.service.serviceCore.BaseInvokeService;
import com.fowo.api.datainterface.util.Common;
import com.fowo.api.datainterface.util.JScriptUtil;
import com.fowo.api.datainterface.util.JsonUtil;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

/**
 * 数据接口 服务实现类
 */
@Service
@Slf4j
@DS("ds24")
@RequiredArgsConstructor
public class EBOEXPServiceImpl implements BaseInvokeService {

    private final Common common;

    private volatile BaseAspect baseAspect;

    public synchronized BaseAspect getBaseAspect(String type) {
        return ObjUtil.isEmpty(baseAspect) ? new BaseAspect(type) : baseAspect;
    }

    private final JScriptUtil jScriptUtil;

    @Override
    public DataTypeKind getType() {
        return DataTypeKind.EBOEXP;
    }

    @Override
    public JSONObject getAuth(DataContextModel.DatainterfaceAuthorityModel invoke) {
        String code = common.getAuthoritySimpleFactory(invoke, Constants.EBOEXP_CODE);
        String token = common.getAuthoritySimpleFactory(invoke, Constants.EBOEXP_TOKEN);
        String SOAPAction = common.getAuthoritySimpleFactory(invoke, Constants.EBOEXP_SOAPACTION);
        String prefix = common.getAuthoritySimpleFactory(invoke, Constants.EBOEXP_PREFIX);
        String namespaceURI = common.getAuthoritySimpleFactory(invoke, Constants.EBOEXP_NAMESPACEURI);
        Assert.isTrue(ObjUtil.isAllNotEmpty(code, token, SOAPAction, prefix), "请配置授权格式,例: {\"code\":\"\",\"token\":\"\",\"SOAPAction\":\"\",\"prefix\":\"\",\"namespaceURI\":\"\"}");
        JSONObject paramsAuth = new JSONObject();
        paramsAuth.put(Constants.EBOEXP_CODE, code);
        paramsAuth.put(Constants.EBOEXP_TOKEN, token);
        paramsAuth.put(Constants.EBOEXP_SOAPACTION, SOAPAction);
        paramsAuth.put(Constants.EBOEXP_PREFIX, prefix);
        paramsAuth.put(Constants.EBOEXP_NAMESPACEURI, namespaceURI);
        return paramsAuth;
    }

    public Object invoke(DataContextModel.DatainterfaceInvokeModel invoke, Object currentParamsMap, JSONObject currentHeadersMap) {
        JSONObject auth = getAuth(invoke.getAuthority());
        if (ObjUtil.isEmpty(currentParamsMap)) {
            currentParamsMap = MapUtil.newHashMap();
        }
        Map<String, Object> params = JsonUtil.getJsonToBean(currentParamsMap, JSONObject.class);
        params.put(Constants.EBOEXP_CODE, MapUtil.getStr(auth, Constants.EBOEXP_CODE));
        params.put(Constants.EBOEXP_TOKEN, MapUtil.getStr(auth, Constants.EBOEXP_TOKEN));
        String path = invoke.getAuthority().getRootPath();
        Object res = null;
        try {
            log.info("执行EBO物流方法字符串入参:{}", JsonUtil.getObjectToString(params));
            Object send = getBaseAspect(invoke.getAuthority().getAppName()).soapRequest(auth, path, invoke.getInterfaceUrl(), params, Constants.Read, StrUtil.EMPTY);
            log.info("执行EBO物流方法字符串出参:{}", send);
            res = XmlUtil.xmlToBean(XmlUtil.readXML(Convert.toStr(send)), JSONObject.class);
        } catch (Exception ex) {
            Assert.isTrue(false, "接口 {} ，地址 {} 错误 {} ！", invoke.getEnCode(), path, StrUtil.subPre(ExceptionUtil.getRootCauseMessage(ex), 1000));
        }
        return jScriptUtil.callJsInvoke(invoke.getDataProcessing(), res == null ? new ArrayList<>() : res, null, null);
    }


//    private static Object request(String method) {
//        Object res = null;
//        String requestId = UUID.randomUUID().toString();
//        Map<String, Object> params = new HashMap<>();
//        params.put("code", "JMYW");
//        params.put("token", "23EC9310695A4EF48FAA8B89D60C5415");
//        try {
//            String url = "http://www.eboexp.com/api/shipping.asmx";
//            SoapClient client = SoapClient.create(url)
//                    .header("SOAPAction", "http://diqisoft.com/GetShippingExpress")
//                    // 设置要请求的方法，此接口方法前缀为web，传入对应的命名空间
//                    .setMethod("diq:" + method, "http://diqisoft.com/")
//                    .setParams(params, true);//此处写true，会自动填写命名空间
//            log.info("[请求ID:{}]测试方法字符串接口:{},入参:{}", requestId, url, client.getMsgStr(true));
//            // 发送请求，参数true表示返回一个格式化后的XML内容
//            // 返回内容为XML字符串，可以配合XmlUtil解析这个响应
//            String send = client.send(false);
//            log.info("[请求ID:{}]测试方法字符串出参:{}", requestId, send);
//            JSONObject resultJSON = XmlUtil.xmlToBean(XmlUtil.readXML(send), JSONObject.class);
//            if (MapUtil.isNotEmpty(resultJSON)) {
//                res = JsonUtil.getJsonToBeanSafe(resultJSON, "$['soap:Envelope']['soap:Body']['GetShippingExpressResponse']", JSONObject.class);
//            }
//            return res;
//        } catch (Exception ex) {
//            log.error("[请求ID:{}]测试方法字符串出现异常,入参:{},出参:{},{}", requestId, params, res, ex);
//            throw ex;
//        }
//    }

}
